#include "bw_slot.h"
#include "public.h"
#include "cJSON.h"
#include "bw_FcgiRequest.h"
#include "bw_jskey.h"
#include "bw_sys.h"
#include "def.h"

using namespace bwcgi;

extern char g_outbuf[];
extern int jsonMsgtoStr(cJSON *pout_root,char *gbuf,unsigned int maxsize);
extern cJSON *retMesgHead(cJSON *root,unsigned int retcode,const char *retmsg);

//********************************************************************************//
// 获取当前正在工作的插槽数目
int slot_num() 
{
	stSUB_BOARD_INFO * sb_info = NULL;
	int boardNum = 0;
	for (int i = 0; i < ENC_MAX_SUB_BOARD; i++) 
	{
		sb_info = &(g_encset_mst->sboard[i]);
		if (sb_info->reg_flag == 1) 
		{
			boardNum++;
		}
	}

	return boardNum;
}

const char* av_slot_num()
{
	cJSON *pout_root = NULL;
	cJSON *p_obj = NULL;

	//int boardNum = slot_num();

	// 构建返回网页的json
	pout_root = cJSON_CreateObject();
	p_obj = retMesgHead(pout_root,0,"SUCCESS");
	
	cJSON_AddNumberToObject(p_obj, "slot_num", BWENC_SLOT_NUM);
	
	jsonMsgtoStr(pout_root,g_outbuf,get_g_oubuf_size());

	cJSON_Delete(pout_root);
	return g_outbuf;
}


// 通道音视频信息获取
const char* av_list(const char* json) 
{
	int s_id = 0;
	eENC_ERROR code = BWENC_ERROR_UNKNOW;
	cJSON* root = cJSON_Parse(json);
	if (!root) 
	{
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		return bwenc_common_ack(code);
	}

	cJSON* param = cJSON_GetObjectItem(root, KEY_PARAM);
	if (!param) {
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}

	// s_id
	cJSON *ptmp = cJSON_GetObjectItem(param, "s_id");
	if(ptmp) 
	{
		s_id = ptmp->valueint;
	}
	cJSON_Delete(root);

//********** response *************//
	//int boardNum = slot_num();

	cJSON *pout_root = NULL;
	cJSON *p_obj = NULL;
	cJSON *p_arr = NULL;
	cJSON *p_tmp = NULL;
	stENC_CHLSET* chl_info = NULL;

	pout_root = cJSON_CreateObject();
	cJSON_AddNumberToObject(pout_root, "retCode", 0);
	cJSON_AddStringToObject(pout_root, "retMsg", "SUCCESS");
	p_obj = cJSON_CreateObject();
	cJSON_AddItemToObject(pout_root, "retData", p_obj);
	p_arr = cJSON_CreateArray();
	cJSON_AddItemToObject(p_obj, "ad_vd_list", p_arr);

	

	for (int i = 0; i < ENC_MAX_SUB_BOARD; i++) 
	{
		if(s_id >=1 && s_id <= ENC_MAX_SUB_BOARD)
		{
			if((i+1) != s_id)
			{
				continue;
			}
		}
		
		for (int j = 0; j < ENC_MAX_CHL; j++) 
		{
			chl_info = &(g_encset_mst->enc_chls[i * ENC_MAX_CHL + j]);
			p_tmp = cJSON_CreateObject();
			cJSON_AddItemToArray(p_arr, p_tmp);
			cJSON_AddNumberToObject(p_tmp, "s_id", i + 1);
			cJSON_AddNumberToObject(p_tmp, "c_id", j + 1);
			if (chl_info->encchl_isrun == 0) 
			{
				cJSON_AddNumberToObject(p_tmp, "is_run", 0);
			} 
			else 
			{
				cJSON_AddNumberToObject(p_tmp, "is_run", 1);
			}

			// 信号锁定状态
			if (chl_info->encchl_errcode == 0) 
			{
				cJSON_AddNumberToObject(p_tmp, "status", 1);
			} 
			else 
			{
				cJSON_AddNumberToObject(p_tmp, "status", 0);
			}

			if (chl_info->encchl_vid.vid_codec == BWENC_VID_CODEC_H264) 
			{
				cJSON_AddStringToObject(p_tmp, "codec", BWENC_VCODEC_H264);
			} 
			else if (chl_info->encchl_vid.vid_codec == BWENC_VID_CODEC_H265) 
			{
				cJSON_AddStringToObject(p_tmp, "codec", BWENC_VCODEC_H265);
			} 
			else if (chl_info->encchl_vid.vid_codec == BWENC_VID_CODEC_NB)
			{
				cJSON_AddStringToObject(p_tmp, "codec", "NB");
			} 
			else 
			{
				cJSON_AddStringToObject(p_tmp, "codec", "-");
			}

			if (chl_info->encchl_vid.vid_profile == BWENC_VID_PROFILE_BASELINE) 
			{
				cJSON_AddStringToObject(p_tmp, "profile", BWENC_VPRO_BASELINE);
			} 
			else if (chl_info->encchl_vid.vid_profile
					== BWENC_VID_PROFILE_MAIN) 
			{
				cJSON_AddStringToObject(p_tmp, "profile", BWENC_VPRO_MAIN);
			} 
			else if (chl_info->encchl_vid.vid_profile
					== BWENC_VID_PROFILE_HIGH) 
			{
				cJSON_AddStringToObject(p_tmp, "profile", BWENC_VPRO_HIGH);
			} 
			else if (chl_info->encchl_vid.vid_profile
					== BWENC_VID_PROFILE_NB) 
			{
				cJSON_AddStringToObject(p_tmp, "profile", "NB");
			} 
			else 
			{
				cJSON_AddStringToObject(p_tmp, "profile", "-");
			}

			// rc_type
			if (chl_info->encchl_vid.vid_rctype == BWENC_VID_RC_ABR) {
				cJSON_AddStringToObject(p_tmp, "rc_type", BWENC_VRC_ABR);
			} else if (chl_info->encchl_vid.vid_rctype == BWENC_VID_RC_CBR) {
				cJSON_AddStringToObject(p_tmp, "rc_type", BWENC_VRC_CBR);
			} else if (chl_info->encchl_vid.vid_profile == BWENC_VID_RC_VBR) {
				cJSON_AddStringToObject(p_tmp, "rc_type", BWENC_VRC_VBR);
			} else if (chl_info->encchl_vid.vid_profile == BWENC_VID_RC_NB) {
				cJSON_AddStringToObject(p_tmp, "rc_type", "NB");
			} else {
				cJSON_AddStringToObject(p_tmp, "rc_type", "-");
			}

			// bitrate
			cJSON_AddNumberToObject(p_tmp, "bitrate",chl_info->encchl_vid.vid_bitrate_kb);

			cJSON_AddNumberToObject(p_tmp, "fluctuate", chl_info->encchl_vid.vid_fluctuate);

			// gop_size
			cJSON_AddNumberToObject(p_tmp, "gop_size",chl_info->encchl_vid.vid_gopsize);

			// output_res
			if (chl_info->encchl_vid.vid_height == BWENC_OUTPUT_WH_1080) 
			{
				cJSON_AddStringToObject(p_tmp, "output_res",BWENC_OUTPUT_HEIGHT_1080_STR);
			} 
			else if (chl_info->encchl_vid.vid_height == BWENC_OUTPUT_WH_720) 
			{
				cJSON_AddStringToObject(p_tmp, "output_res",BWENC_OUTPUT_HEIGHT_720_STR);
			} 
			else if (chl_info->encchl_vid.vid_height == BWENC_OUTPUT_WH_576) 
			{
				cJSON_AddStringToObject(p_tmp, "output_res",BWENC_OUTPUT_HEIGHT_576_STR);
			} 
			else if (chl_info->encchl_vid.vid_height == BWENC_OUTPUT_WH_480) 
			{
				cJSON_AddStringToObject(p_tmp, "output_res",BWENC_OUTPUT_HEIGHT_480_STR);
			} 
			else 
			{
				cJSON_AddStringToObject(p_tmp, "output_res", "");
			}

			// ad_codec
			if (BWENC_AUD_CODEC_MP2 == chl_info->encchl_aud.aud_codec) 
			{
				cJSON_AddStringToObject(p_tmp, "ad_codec", BWENC_ACODEC_MP2);
			} 
			else if (BWENC_AUD_CODEC_AAC_LC
					== chl_info->encchl_aud.aud_codec) 
			{
				cJSON_AddStringToObject(p_tmp, "ad_codec", BWENC_ACODEC_LC_AAC);
			} 
			else if (BWENC_AUD_CODEC_AAC_HE
					== chl_info->encchl_aud.aud_codec) 
			{
				cJSON_AddStringToObject(p_tmp, "ad_codec", BWENC_ACODEC_HE_AAC);
			} 
			else if (BWENC_AUD_CODEC_NB == chl_info->encchl_aud.aud_codec) 
			{
				cJSON_AddStringToObject(p_tmp, "ad_codec", "NB");
			} 
			else 
			{
				cJSON_AddStringToObject(p_tmp, "ad_codec", "-");
			}

			// ad_bitrate
			cJSON_AddNumberToObject(p_tmp, "ad_bitrate",
					chl_info->encchl_aud.aud_bitrate_kb);

			// ad_gain
			double ad_gain = 1.0 * chl_info->encchl_aud.aud_vol / 100;
			cJSON_AddNumberToObject(p_tmp, "ad_gain", ad_gain);
		}
	}

	jsonMsgtoStr(pout_root,g_outbuf,get_g_oubuf_size());

	cJSON_Delete(pout_root);
	return g_outbuf;
}

// 通道音视频信息编辑
const char* av_edit(const char* json) 
{
	char logstr[SZ_1K] = {0};
	eENC_ERROR code = BWENC_ERROR_UNKNOW;
	
	cJSON* root = cJSON_Parse(json);
	if (!root) {
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		return bwenc_common_ack(code);
	}

	cJSON* param = cJSON_GetObjectItem(root, KEY_PARAM);
	if (!param) {
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}

	// s_id
	cJSON *p_tmp = cJSON_GetObjectItem(param, "s_id");
	if (!p_tmp || p_tmp->valueint <= 0 || p_tmp->valueint > ENC_MAX_SUB_BOARD) {
		cgi_debug("s_id error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int s_id = p_tmp->valueint;

	// c_id
	p_tmp = cJSON_GetObjectItem(param, "c_id");
	if (!p_tmp || p_tmp->valueint <= 0 || p_tmp->valueint > ENC_MAX_CHL) {
		cgi_debug("c_id error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int c_id = p_tmp->valueint;

	int chl_index = (s_id - 1) * ENC_MAX_CHL + c_id - 1;

	// codec
	int codec;
	p_tmp = cJSON_GetObjectItem(param, "codec");
	if (!p_tmp || !p_tmp->valuestring || strlen(p_tmp->valuestring) <= 0) {
		cgi_debug("codec empty");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	if (0 == strcmp(BWENC_VCODEC_H264, p_tmp->valuestring)) 
	{
		codec = BWENC_VID_CODEC_H264;
	} 
	else if (0 == strcmp(BWENC_VCODEC_H265, p_tmp->valuestring)) 
	{
		codec = BWENC_VID_CODEC_H265;
	} 
	else 
	{
		cgi_debug("codec error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}

	// profile
	int profile;
	p_tmp = cJSON_GetObjectItem(param, "profile");
	if (!p_tmp || !p_tmp->valuestring || strlen(p_tmp->valuestring) <= 0) 
	{
		cgi_debug("profile empty");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	if (0 == strcmp(BWENC_VPRO_HIGH, p_tmp->valuestring)) 
	{
		profile = BWENC_VID_PROFILE_HIGH;
	} else if (0 == strcmp(BWENC_VPRO_MAIN, p_tmp->valuestring)) {
		profile = BWENC_VID_PROFILE_MAIN;
	} else if (0 == strcmp(BWENC_VPRO_BASELINE, p_tmp->valuestring)) {
		profile = BWENC_VID_PROFILE_BASELINE;
	} else {
		cgi_debug("profile error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}

	// rc_type
	int rc_type;
	p_tmp = cJSON_GetObjectItem(param, "rc_type");
	if (!p_tmp || !p_tmp->valuestring || strlen(p_tmp->valuestring) <= 0) {
		cgi_debug("rc_type empty");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	cgi_debug("rc_type :%s", p_tmp->valuestring);
	if (0 == strcmp(BWENC_VRC_VBR, p_tmp->valuestring)) {
		rc_type = BWENC_VID_RC_VBR;
	} else if (0 == strcmp(BWENC_VRC_CBR, p_tmp->valuestring)) {
		rc_type = BWENC_VID_RC_CBR;
	} else if (0 == strcmp(BWENC_VRC_ABR, p_tmp->valuestring)) {
		rc_type = BWENC_VID_RC_ABR;
	} else {
		cgi_debug("rc_type error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	cgi_debug("rc_type :%d", rc_type);

	// bitrate
	p_tmp = cJSON_GetObjectItem(param, "bitrate");
	if (!p_tmp || p_tmp->valueint <= 0) {
		cgi_debug("bitrate error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int bitrate = p_tmp->valueint;

	// fluctuate
	p_tmp = cJSON_GetObjectItem(param, "fluctuate");
	if (!p_tmp || p_tmp->valueint <= 0 || p_tmp->valueint > 100) {
		cgi_debug("fluctuate error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int fluctuate = p_tmp->valueint;

	int max_bitrate = bitrate * (1 + 1.0 * fluctuate / 100);  // 最大码率
	int min_bitrate = bitrate * (1 - 1.0 * fluctuate / 100); // 最小码率

	// gop_size
	p_tmp = cJSON_GetObjectItem(param, "gop_size");
	if (!p_tmp || p_tmp->valueint <= 0) {
		cgi_debug("gop_size error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int gop_size = p_tmp->valueint;

	int output_width = 0;
	int output_height = 0;
	p_tmp = cJSON_GetObjectItem(param, "output_res");
	if (!p_tmp || !p_tmp->valuestring || strlen(p_tmp->valuestring) <= 0) 
	{
		cgi_debug("output_res error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	if (0 == strcmp(BWENC_OUTPUT_HEIGHT_1080_STR, p_tmp->valuestring)) 
	{
		output_width = BWENC_OUTPUT_WH_1920;
		output_height = BWENC_OUTPUT_WH_1080;
	} 
	else if (0 == strcmp(BWENC_OUTPUT_HEIGHT_720_STR, p_tmp->valuestring)) 
	{
		output_width = BWENC_OUTPUT_WH_1280;
		output_height = BWENC_OUTPUT_WH_720;
	} 
	else if (0 == strcmp(BWENC_OUTPUT_HEIGHT_576_STR, p_tmp->valuestring)) 
	{
		output_width = BWENC_OUTPUT_WH_720;
		output_height = BWENC_OUTPUT_WH_576;
	} 
	else if (0 == strcmp(BWENC_OUTPUT_HEIGHT_480_STR, p_tmp->valuestring)) 
	{
		output_width = BWENC_OUTPUT_WH_720;
		output_height = BWENC_OUTPUT_WH_480;
	} 
	else 
	{
		cgi_debug("output_res value error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}

	// ad_codec
	int ad_codec;
	p_tmp = cJSON_GetObjectItem(param, "ad_codec");
	if (!p_tmp || !p_tmp->valuestring || strlen(p_tmp->valuestring) <= 0) 
	{
		cgi_debug("ad_codec empty");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	if (0 == strcmp(BWENC_ACODEC_HE_AAC, p_tmp->valuestring)) 
	{
		ad_codec = BWENC_AUD_CODEC_AAC_HE;
	} 
	else if (0 == strcmp(BWENC_ACODEC_LC_AAC, p_tmp->valuestring)) 
	{
		ad_codec = BWENC_AUD_CODEC_AAC_LC;
	} 
	else if (0 == strcmp(BWENC_ACODEC_MP2, p_tmp->valuestring)) 
	{
		ad_codec = BWENC_AUD_CODEC_MP2;
	} 
	else 
	{
		cgi_debug("ad_codec error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}

	// ad_bitrate
	p_tmp = cJSON_GetObjectItem(param, "ad_bitrate");
	if (!p_tmp || p_tmp->valueint <= 0) 
	{
		cgi_debug("ad_bitrate error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int ad_bitrate = p_tmp->valueint;

	// ad_gain
	p_tmp = cJSON_GetObjectItem(param, "ad_gain");
	if (!p_tmp || p_tmp->valuedouble <= 0) 
	{
		cgi_debug("ad_gain error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	double ad_gain = p_tmp->valuedouble;

	sem_wait(g_shrmsem);
	stENC_CHLSET* chl_info = &(g_encset_mst->enc_chls[chl_index]);
	chl_info->encchl_vid.vid_codec = codec;
	chl_info->encchl_vid.vid_profile = profile;
	chl_info->encchl_vid.vid_rctype = rc_type;
	chl_info->encchl_vid.vid_bitrate_kb = bitrate;
	chl_info->encchl_vid.vid_fluctuate = fluctuate;
	
	chl_info->encchl_vid.vid_bitrate_max = max_bitrate;
	chl_info->encchl_vid.vid_bitrate_min = min_bitrate;
	chl_info->encchl_vid.vid_gopsize = gop_size;
	chl_info->encchl_vid.vid_width = output_width;
	chl_info->encchl_vid.vid_height = output_height;
	chl_info->encchl_aud.aud_codec = ad_codec;
	chl_info->encchl_aud.aud_bitrate_kb = ad_bitrate;
	chl_info->encchl_aud.aud_vol = ad_gain * 100;
	chl_info->encchl_setvsion++;
	sem_post(g_shrmsem);

	cJSON_Delete(root);
	snprintf(logstr,sizeof(logstr),"slot:%d-ch:%d Audio/Video info modified successfully",s_id,c_id);
	log_write(BWENC_LOG_SYS_SET, logstr);
	return bwenc_common_ack(BWENC_ERROR_NONE);
}

// 通道TS信息获取
const char* ts_list(const char* json) 
{
	int s_id = 0;
	eENC_ERROR code = BWENC_ERROR_UNKNOW;
	cJSON* root = cJSON_Parse(json);
	if (!root) 
	{
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		return bwenc_common_ack(code);
	}

	cJSON* param = cJSON_GetObjectItem(root, KEY_PARAM);
	if (!param) {
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}

	// s_id
	cJSON *ptmp = cJSON_GetObjectItem(param, "s_id");
	if(ptmp) 
	{
		s_id = ptmp->valueint;
	}
	cJSON_Delete(root);

//***************response**************
	//int boardNum = slot_num();

	cJSON *pout_root = NULL;
	cJSON *p_obj = NULL;
	cJSON *p_arr = NULL;
	cJSON *p_tmp = NULL;
	stENC_CHLSET* chl_info = NULL;

	pout_root = cJSON_CreateObject();
	cJSON_AddNumberToObject(pout_root, "retCode", 0);
	cJSON_AddStringToObject(pout_root, "retMsg", "SUCCESS");
	p_obj = cJSON_CreateObject();
	cJSON_AddItemToObject(pout_root, "retData", p_obj);
	p_arr = cJSON_CreateArray();
	cJSON_AddItemToObject(p_obj, "ts_list", p_arr);

	for (int i = 0; i < ENC_MAX_SUB_BOARD; i++) 
	{
		if(s_id >=1 && s_id <= ENC_MAX_SUB_BOARD)
		{
			if((i+1) != s_id)
			{
				continue;
			}
		}
		
		for (int j = 0; j < ENC_MAX_CHL; j++) 
		{
			int index = i * ENC_MAX_CHL + j;
			chl_info = &(g_encset_mst->enc_chls[index]);
			p_tmp = cJSON_CreateObject();
			cJSON_AddItemToArray(p_arr, p_tmp);
			cJSON_AddNumberToObject(p_tmp, "s_id", i + 1);
			cJSON_AddNumberToObject(p_tmp, "c_id", j + 1);
			if (chl_info->encchl_isrun == 0) {
				cJSON_AddNumberToObject(p_tmp, "is_run", 0);
			} else {
				cJSON_AddNumberToObject(p_tmp, "is_run", 1);
			}

			// status
			if (chl_info->encchl_errcode == 0) {
				cJSON_AddNumberToObject(p_tmp, "status", 1);
			} else {
				cJSON_AddNumberToObject(p_tmp, "status", 0);
			}

			char tmpbuf[ENC_SERVICE_NAME_LEN];
			memcpy(tmpbuf, chl_info->encchl_ts.ts_service_name,
					sizeof(chl_info->encchl_ts.ts_service_name));
			cJSON_AddStringToObject(p_tmp, "srv_name", tmpbuf);

			memcpy(tmpbuf, chl_info->encchl_ts.ts_provider_name,
					sizeof(chl_info->encchl_ts.ts_provider_name));
			cJSON_AddStringToObject(p_tmp, "srv_provider", tmpbuf);

			cJSON_AddNumberToObject(p_tmp, "srv_id",
					chl_info->encchl_ts.ts_service_id);

			cJSON_AddNumberToObject(p_tmp, "pcr_interval",
					chl_info->encchl_ts.ts_pcr_interval_ms);

			cJSON_AddNumberToObject(p_tmp, "pcr_pid",
					chl_info->encchl_ts.ts_pcr_pid);

			cJSON_AddNumberToObject(p_tmp, "v_pid",
					chl_info->encchl_ts.ts_vid_pid);

			cJSON_AddNumberToObject(p_tmp, "pmt_pid",
					chl_info->encchl_ts.ts_pmt_pid);

			cJSON_AddNumberToObject(p_tmp, "a_pid",
					chl_info->encchl_ts.ts_aud_pid);

			cJSON_AddNumberToObject(p_tmp, "ts_bitrate",
					chl_info->encchl_ts.ts_muxrate_kb);
		}
	}
	
	jsonMsgtoStr(pout_root,g_outbuf,get_g_oubuf_size());

	cJSON_Delete(pout_root);
	return g_outbuf;
}

// 通道TS信息编辑
const char* ts_edit(const char* json) 
{
	char logstr[SZ_1K] = {0};
	eENC_ERROR code = BWENC_ERROR_UNKNOW;
	
	cJSON* root = cJSON_Parse(json);
	if (!root) {
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		return bwenc_common_ack(code);
	}

	cJSON* param = cJSON_GetObjectItem(root, KEY_PARAM);
	if (!param) {
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}

	// s_id
	cJSON *p_tmp = cJSON_GetObjectItem(param, "s_id");
	if (!p_tmp || p_tmp->valueint <= 0 || p_tmp->valueint > ENC_MAX_SUB_BOARD) {
		cgi_debug("s_id error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int s_id = p_tmp->valueint;

	// c_id
	p_tmp = cJSON_GetObjectItem(param, "c_id");
	if (!p_tmp || p_tmp->valueint <= 0 || p_tmp->valueint > ENC_MAX_CHL) {
		cgi_debug("c_id error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int c_id = p_tmp->valueint;

	int chl_index = (s_id - 1) * ENC_MAX_CHL + c_id - 1;

	// srv_name
	p_tmp = cJSON_GetObjectItem(param, "srv_name");
	if (!p_tmp || !p_tmp->valuestring
			|| strlen(p_tmp->valuestring)
					<= 0||strlen(p_tmp->valuestring)>ENC_SERVICE_NAME_LEN) {
		cgi_debug("srv_name error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	char srv_name[ENC_SERVICE_NAME_LEN] = { '\0' };
	memcpy(srv_name, p_tmp->valuestring, strlen(p_tmp->valuestring));

	// srv_provider
	p_tmp = cJSON_GetObjectItem(param, "srv_provider");
	if (!p_tmp || !p_tmp->valuestring
			|| strlen(p_tmp->valuestring)
					<= 0||strlen(p_tmp->valuestring)>ENC_PROVIDER_NAME_LEN) {
		cgi_debug("srv_name error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	char srv_provider[ENC_PROVIDER_NAME_LEN] = { '\0' };
	memcpy(srv_provider, p_tmp->valuestring, strlen(p_tmp->valuestring));

	// srv_id
	p_tmp = cJSON_GetObjectItem(param, "srv_id");
	if (!p_tmp || p_tmp->valueint < 0) {
		cgi_debug("srv_id error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int srv_id = p_tmp->valueint;

	// pcr_interval
	p_tmp = cJSON_GetObjectItem(param, "pcr_interval");
	if (!p_tmp || p_tmp->valueint < 0) {
		cgi_debug("pcr_interval error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int pcr_interval = p_tmp->valueint;

	// pcr_pid
	p_tmp = cJSON_GetObjectItem(param, "pcr_pid");
	if (!p_tmp || p_tmp->valueint < 32 || p_tmp->valueint > 8190) {
		cgi_debug("pcr_pid error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int pcr_pid = p_tmp->valueint;

	// v_pid
	p_tmp = cJSON_GetObjectItem(param, "v_pid");
	if (!p_tmp || p_tmp->valueint < 32 || p_tmp->valueint > 8190) {
		cgi_debug("v_pid error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int v_pid = p_tmp->valueint;

	// pmt_pid
	p_tmp = cJSON_GetObjectItem(param, "pmt_pid");
	if (!p_tmp || p_tmp->valueint < 32 || p_tmp->valueint > 8190
			|| p_tmp->valueint == v_pid || p_tmp->valueint == pcr_pid) {
		cgi_debug("pmt_pid error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int pmt_pid = p_tmp->valueint;

	// a_pid
	p_tmp = cJSON_GetObjectItem(param, "a_pid");
	if (!p_tmp || p_tmp->valueint < 32 || p_tmp->valueint > 8190
			|| p_tmp->valueint == v_pid || p_tmp->valueint == pcr_pid
			|| p_tmp->valueint == pmt_pid) {
		cgi_debug("a_pid error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int a_pid = p_tmp->valueint;

	// ts_bitrate
	p_tmp = cJSON_GetObjectItem(param, "ts_bitrate");
	if (!p_tmp || p_tmp->valueint <= 0) {
		cgi_debug("ts_bitrate error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int ts_bitrate = p_tmp->valueint;

	sem_wait(g_shrmsem);
	stENC_CHLSET* chl_info = &(g_encset_mst->enc_chls[chl_index]);
	memcpy(chl_info->encchl_ts.ts_service_name, srv_name, sizeof(srv_name));
	memcpy(chl_info->encchl_ts.ts_provider_name, srv_provider,
			sizeof(srv_provider));
	chl_info->encchl_ts.ts_service_id = srv_id;
	chl_info->encchl_ts.ts_pcr_interval_ms = pcr_interval;
	chl_info->encchl_ts.ts_pcr_pid = pcr_pid;
	chl_info->encchl_ts.ts_vid_pid = v_pid;
	chl_info->encchl_ts.ts_pmt_pid = pmt_pid;
	chl_info->encchl_ts.ts_aud_pid = a_pid;
	chl_info->encchl_ts.ts_muxrate_kb = ts_bitrate;
	chl_info->encchl_setvsion++;
	sem_post(g_shrmsem);

	cJSON_Delete(root);
	snprintf(logstr,sizeof(logstr),"slot:%d-ch:%d TS info modified successfully",s_id,c_id);
	log_write(BWENC_LOG_SYS_SET, logstr);
	return bwenc_common_ack(BWENC_ERROR_NONE);
}

// 通道开启/关闭
const char* change_run(const char* json) 
{
	char logstr[SZ_1K] = {0};
	eENC_ERROR code = BWENC_ERROR_UNKNOW;
	cJSON* root = cJSON_Parse(json);
	if (!root) {
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		return bwenc_common_ack(code);
	}

	cJSON* param = cJSON_GetObjectItem(root, KEY_PARAM);
	if (!param) {
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}

	// s_id
	cJSON *p_tmp = cJSON_GetObjectItem(param, "s_id");
	if (!p_tmp || p_tmp->valueint <= 0 || p_tmp->valueint > ENC_MAX_SUB_BOARD) {
		cgi_debug("s_id error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int s_id = p_tmp->valueint;

	// c_id
	p_tmp = cJSON_GetObjectItem(param, "c_id");
	if (!p_tmp || p_tmp->valueint <= 0 || p_tmp->valueint > ENC_MAX_CHL) {
		cgi_debug("c_id error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int c_id = p_tmp->valueint;

	// type
	p_tmp = cJSON_GetObjectItem(param, "type");
	if (!p_tmp || (p_tmp->valueint != 0 && p_tmp->valueint != 1)) {
		cgi_debug("type error");
		code = BWENC_ERROR_INVALID_PARAM;
		cJSON_Delete(root);
		return bwenc_common_ack(code);
	}
	int type = p_tmp->valueint;

	int chl_index = (s_id - 1) * ENC_MAX_CHL + c_id - 1;

	sem_wait(g_shrmsem);
	stENC_CHLSET* chl_info = &(g_encset_mst->enc_chls[chl_index]);
	if (type == 1) 
	{
		chl_info->encchl_isrun = 1;
	} 
	else 
	{
		chl_info->encchl_isrun = 0;
	}
	chl_info->encchl_setvsion++;
	sem_post(g_shrmsem);

	if (type == 0) 
	{
		snprintf(logstr,sizeof(logstr),"slot:%d-ch:%d Audio/Video/TS closed successfully",s_id,c_id);
		log_write(BWENC_LOG_SYS_SET, logstr);
	} 
	else 
	{
		snprintf(logstr,sizeof(logstr),"slot:%d-ch:%d Audio/Video/TS opened successfully",s_id,c_id);
		log_write(BWENC_LOG_SYS_SET, logstr);
	}
	
	cJSON_Delete(root);
	return bwenc_common_ack(BWENC_ERROR_NONE);
}

//******************************************************************************//
//获取卡槽的识别状态；
const char* get_slot_status(unsigned int s_id) 
{
	cJSON *pout_root = NULL;
	cJSON *p_obj = NULL;
	//cJSON *p_arr = NULL;
	
	int slotflg = 0;

	stSUB_BOARD_INFO * sb_info = NULL;
	// 构建返回网页的json
	pout_root = cJSON_CreateObject();
	p_obj = retMesgHead(pout_root,0,"SUCCESS");

	if(s_id < 1 || s_id > ENC_MAX_SUB_BOARD)
	{
		s_id = 1;
	}
	
	sb_info = &(g_encset_mst->sboard[s_id - 1]);
		
	if((0 == sb_info->reg_flag) || (0 == sb_info->status))
	{
		slotflg = 0;
	}
	else
	{
		slotflg = 1;
	}
	
	cJSON_AddNumberToObject(p_obj, "s_id", s_id);
	cJSON_AddNumberToObject(p_obj, "reg_flag", slotflg);

	jsonMsgtoStr(pout_root,g_outbuf,get_g_oubuf_size());

	cJSON_Delete(pout_root);
	return g_outbuf;
}

const char* av_slot_status(const char* json) 
{
	unsigned int s_id = 0;
	eENC_ERROR code = BWENC_ERROR_NONE;
	cJSON *p_tmp = NULL;
	cJSON* param = NULL;
	
	cJSON* root = cJSON_Parse(json);
	if (!root) 
	{
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		return bwenc_common_ack(code);
	}

	param = cJSON_GetObjectItem(root, KEY_PARAM);
	if (!param) 
	{
		cgi_debug("error");
		code = BWENC_ERROR_INVALID_PARAM;
		goto error;
	}

	// s_id
	p_tmp = cJSON_GetObjectItem(param, "s_id");
	if (!p_tmp || p_tmp->valueint <= 0 || p_tmp->valueint > ENC_MAX_SUB_BOARD)  
	{
		cgi_debug("s_id error");
		code = BWENC_ERROR_INVALID_PARAM;
		goto error;
	}
	
	s_id = p_tmp->valueint;

	cJSON_Delete(root);
	return get_slot_status(s_id);
error:
	cJSON_Delete(root);
	return bwenc_common_ack(code);
}

